<?php

namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Database\Eloquent\Relations\BelongsTo;
use Illuminate\Database\Eloquent\Relations\HasMany;
use Illuminate\Support\Facades\DB;
use App\Notifications\OrderStatusChanged;

class Order extends Model
{
    use HasFactory;

    protected $fillable = [
        'user_id',
        'order_number',
        'status',
        'extended_status',
        'total_amount',
        'subtotal_amount',
        'shipping_fee',
        'discount_amount',
        'user_coupon_id',
        'receiver_name',
        'receiver_phone',
        'receiver_address',
        'payment_method',
        'payment_status',
        'notes',
        'tracking_number',
        'shipping_company',
        'shipping_note',
        'paid_at',
        'shipped_at',
        'delivered_at',
        'cancelled_at',
        'cancel_reason',
        'status_history',
        'status_changed_at',
        'status_changed_by',
        'status_change_reason',
    ];

    protected $casts = [
        'total_amount' => 'decimal:2',
        'subtotal_amount' => 'decimal:2',
        'shipping_fee' => 'decimal:2',
        'discount_amount' => 'decimal:2',
        'paid_at' => 'datetime',
        'shipped_at' => 'datetime',
        'delivered_at' => 'datetime',
        'cancelled_at' => 'datetime',
        'status_history' => 'array',
        'status_changed_at' => 'datetime',
    ];

    /**
     * 默认预加载的关系
     */
    protected $with = ['user'];

    /**
     * 获取路由模型绑定的路由键名称
     */
    public function getRouteKeyName(): string
    {
        return 'order_number';
    }

    /**
     * 基础订单状态常量
     */
    const STATUS_PENDING = 'pending';        // 待支付
    const STATUS_PROCESSING = 'processing';  // 处理中（已支付，待发货）
    const STATUS_SHIPPED = 'shipped';        // 已发货
    const STATUS_DELIVERED = 'delivered';    // 已送达
    const STATUS_CANCELLED = 'cancelled';    // 已取消
    
    /**
     * 扩展状态常量
     */
    const EXTENDED_STATUS_PARTIALLY_SHIPPED = 'partially_shipped';  // 部分发货
    const EXTENDED_STATUS_COMPLETED = 'completed';                  // 已完成
    const EXTENDED_STATUS_REFUNDED = 'refunded';                   // 已退款
    const EXTENDED_STATUS_RETURNED = 'returned';                    // 已退货
    const EXTENDED_STATUS_PARTIALLY_REFUNDED = 'partially_refunded'; // 部分退款
    const EXTENDED_STATUS_PARTIALLY_RETURNED = 'partially_returned'; // 部分退货

    /**
     * 支付方式常量
     */
    const PAYMENT_METHOD_ALIPAY = 'alipay';   // 支付宝
    const PAYMENT_METHOD_WECHAT = 'wechat';  // 微信支付
    const PAYMENT_METHOD_COD = 'cod';       // 货到付款

    /**
     * 支付状态常量
     */
    const PAYMENT_PENDING = 'pending';   // 待支付
    const PAYMENT_PAID = 'paid';        // 已支付
    const PAYMENT_FAILED = 'failed';    // 支付失败
    const PAYMENT_REFUNDED = 'refunded'; // 已退款
    const PAYMENT_COD_CONFIRMED = 'cod_confirmed'; // 货到付款已确认

    /**
     * 关联用户
     */
    public function user(): BelongsTo
    {
        return $this->belongsTo(User::class);
    }

    /**
     * 关联订单项
     */
    public function items(): HasMany
    {
        return $this->hasMany(OrderItem::class);
    }

    /**
     * 关联支付记录
     */
    public function payments(): HasMany
    {
        return $this->hasMany(Payment::class);
    }

    /**
     * 关联售后请求
     */
    public function afterSalesRequests(): HasMany
    {
        return $this->hasMany(AfterSalesRequest::class);
    }

    /**
     * 关联使用的优惠券
     */
    public function userCoupon(): BelongsTo
    {
        return $this->belongsTo(UserCoupon::class);
    }

    /**
     * 获取最新支付记录
     */
    public function latestPayment(): BelongsTo
    {
        return $this->belongsTo(Payment::class, 'id', 'order_id')
            ->latest();
    }

    /**
     * 获取订单状态文本
     */
    public function getStatusTextAttribute(): string
    {
        return match($this->status) {
            self::STATUS_PENDING => '待支付',
            self::STATUS_PROCESSING => '待发货',
            self::STATUS_SHIPPED => '已发货',
            self::STATUS_DELIVERED => '已送达',
            self::STATUS_CANCELLED => '已取消',
            default => '未知状态',
        };
    }

    /**
     * 获取支付状态文本
     */
    public function getPaymentStatusTextAttribute(): string
    {
        return match($this->payment_status) {
            self::PAYMENT_PENDING => '待支付',
            self::PAYMENT_PAID => '已支付',
            self::PAYMENT_FAILED => '支付失败',
            self::PAYMENT_REFUNDED => '已退款',
            self::PAYMENT_COD_CONFIRMED => '货到付款已确认',
            default => '未知状态',
        };
    }

    /**
     * 是否可以支付
     */
    public function canPay(): bool
    {
        return $this->status === self::STATUS_PENDING 
            && $this->payment_status === self::PAYMENT_PENDING;
    }

    /**
     * 是否可以取消
     */
    public function canCancel(): bool
    {
        return in_array($this->status, [self::STATUS_PENDING, self::STATUS_PROCESSING]);
    }

    /**
     * 是否可以发货
     */
    public function canShip(): bool
    {
        return $this->status === self::STATUS_PROCESSING 
            && $this->payment_status === self::PAYMENT_PAID;
    }

    /**
     * 是否可以确认收货
     */
    public function canConfirmDelivery(): bool
    {
        return $this->status === self::STATUS_SHIPPED;
    }

    /**
     * 是否可以申请售后
     */
    public function canApplyAfterSales(): bool
    {
        return in_array($this->status, [
            self::STATUS_PROCESSING,
            self::STATUS_SHIPPED,
            self::STATUS_DELIVERED
        ]) && $this->payment_status === self::PAYMENT_PAID;
    }

    /**
     * 是否可以修改地址
     */
    public function canModifyAddress(): bool
    {
        return $this->status === self::STATUS_PENDING 
            && $this->payment_status === self::PAYMENT_PENDING;
    }

    /**
     * 是否可以修改备注
     */
    public function canModifyNotes(): bool
    {
        return in_array($this->status, [
            self::STATUS_PENDING,
            self::STATUS_PROCESSING
        ]);
    }

    /**
     * 是否可以申请退款
     */
    public function canRefund(): bool
    {
        return in_array($this->status, [
            self::STATUS_PENDING,
            self::STATUS_PROCESSING,
            self::STATUS_SHIPPED,
            self::STATUS_DELIVERED
        ]) && $this->payment_status === self::PAYMENT_PAID;
    }

    /**
     * 是否可以重新发货
     */
    public function canReship(): bool
    {
        return $this->status === self::STATUS_SHIPPED 
            && $this->payment_status === self::PAYMENT_PAID;
    }

    /**
     * 是否可以查看物流
     */
    public function canTrackShipping(): bool
    {
        return in_array($this->status, [
            self::STATUS_SHIPPED,
            self::STATUS_DELIVERED
        ]) && !empty($this->tracking_number);
    }

    /**
     * 是否有售后请求
     */
    public function hasAfterSales(): bool
    {
        return $this->afterSalesRequests()->exists();
    }

    /**
     * 是否有待处理的售后请求
     */
    public function hasPendingAfterSales(): bool
    {
        return $this->afterSalesRequests()
            ->whereIn('status', [AfterSalesRequest::STATUS_PENDING, AfterSalesRequest::STATUS_APPROVED, AfterSalesRequest::STATUS_PROCESSING])
            ->exists();
    }

    /**
     * 是否有已完成的售后请求
     */
    public function hasCompletedAfterSales(): bool
    {
        return $this->afterSalesRequests()
            ->where('status', AfterSalesRequest::STATUS_COMPLETED)
            ->exists();
    }

    /**
     * 获取售后请求统计
     */
    public function getAfterSalesStats(): array
    {
        $stats = $this->afterSalesRequests()
            ->selectRaw('status, COUNT(*) as count')
            ->groupBy('status')
            ->pluck('count', 'status')
            ->toArray();

        return [
            'total' => array_sum($stats),
            'pending' => $stats[AfterSalesRequest::STATUS_PENDING] ?? 0,
            'approved' => $stats[AfterSalesRequest::STATUS_APPROVED] ?? 0,
            'rejected' => $stats[AfterSalesRequest::STATUS_REJECTED] ?? 0,
            'processing' => $stats[AfterSalesRequest::STATUS_PROCESSING] ?? 0,
            'completed' => $stats[AfterSalesRequest::STATUS_COMPLETED] ?? 0,
            'cancelled' => $stats[AfterSalesRequest::STATUS_CANCELLED] ?? 0,
        ];
    }

    /**
     * 标记为已支付
     */
    public function markAsPaid(): void
    {
        $this->updateStatus([
            'payment_status' => self::PAYMENT_PAID,
            'status' => self::STATUS_PROCESSING,
            'paid_at' => now(),
        ], '支付成功', '订单支付成功');
    }

    /**
     * 标记为已发货
     */
    public function markAsShipped(array $shippingData = []): void
    {
        if (!$this->canShip()) {
            throw new \Exception('订单状态不允许发货');
        }

        $updateData = [
            'status' => self::STATUS_SHIPPED,
            'shipped_at' => now(),
        ];

        // 添加物流信息
        if (!empty($shippingData['tracking_number'])) {
            $updateData['tracking_number'] = $shippingData['tracking_number'];
        }
        if (!empty($shippingData['shipping_company'])) {
            $updateData['shipping_company'] = $shippingData['shipping_company'];
        }
        if (!empty($shippingData['shipping_note'])) {
            $updateData['shipping_note'] = $shippingData['shipping_note'];
        }

        $this->updateStatus($updateData, '发货', $shippingData['reason'] ?? '订单发货');
    }
    
    /**
     * 更新订单状态（带历史记录）
     */
    public function updateStatus(array $data, string $action, string $reason = null, string $operator = null): void
    {
        // 记录状态变更历史
        $history = $this->status_history ?? [];
        $history[] = [
            'from_status' => $this->status,
            'from_extended_status' => $this->extended_status,
            'to_status' => $data['status'] ?? $this->status,
            'to_extended_status' => $data['extended_status'] ?? $this->extended_status,
            'action' => $action,
            'reason' => $reason,
            'operator' => $operator ?? auth()->user()?->name ?? '系统',
            'timestamp' => now()->toISOString(),
        ];

        // 更新状态相关字段
        $data['status_history'] = $history;
        $data['status_changed_at'] = now();
        $data['status_changed_by'] = $operator ?? auth()->user()?->name ?? '系统';
        $data['status_change_reason'] = $reason;

        $this->update($data);
        
        // 发送通知
        $this->user->notify(new OrderStatusChanged($this));
    }
    
    /**
     * 获取状态显示文本
     */
    public function getStatusDisplayAttribute(): string
    {
        $statusMap = [
            self::STATUS_PENDING => '待支付',
            self::STATUS_PROCESSING => '待发货',
            self::STATUS_SHIPPED => '已发货',
            self::STATUS_DELIVERED => '已送达',
            self::STATUS_CANCELLED => '已取消',
        ];

        $extendedStatusMap = [
            self::EXTENDED_STATUS_PARTIALLY_SHIPPED => '部分发货',
            self::EXTENDED_STATUS_COMPLETED => '已完成',
            self::EXTENDED_STATUS_REFUNDED => '已退款',
            self::EXTENDED_STATUS_RETURNED => '已退货',
            self::EXTENDED_STATUS_PARTIALLY_REFUNDED => '部分退款',
            self::EXTENDED_STATUS_PARTIALLY_RETURNED => '部分退货',
        ];

        $baseStatus = $statusMap[$this->status] ?? $this->status;
        
        // 处理扩展状态
        if ($this->extended_status) {
            $extendedStatus = $extendedStatusMap[$this->extended_status] ?? $this->extended_status;
            $baseStatus = "{$baseStatus} ({$extendedStatus})";
        }

        // 添加售后状态信息
        if ($this->hasPendingAfterSales()) {
            $baseStatus .= ' [有售后]';
        }

        return $baseStatus;
    }

    /**
     * 获取详细状态信息（包含售后统计）
     */
    public function getDetailedStatusAttribute(): array
    {
        $baseStatus = $this->getStatusTextAttribute();
        $afterSalesStats = $this->getAfterSalesStats();
        
        return [
            'base_status' => $baseStatus,
            'extended_status' => $this->extended_status,
            'payment_status' => $this->getPaymentStatusTextAttribute(),
            'has_after_sales' => $this->hasAfterSales(),
            'has_pending_after_sales' => $this->hasPendingAfterSales(),
            'after_sales_stats' => $afterSalesStats,
            'display_text' => $this->getStatusDisplayAttribute(),
        ];
    }

    /**
     * 标记为已送达
     */
    public function markAsDelivered(): void
    {
        if (!$this->canConfirmDelivery()) {
            throw new \Exception('订单状态不允许确认收货');
        }

        $this->update([
            'status' => self::STATUS_DELIVERED,
            'delivered_at' => now(),
        ]);
    }

    /**
     * 取消订单
     */
    public function cancel(string $reason = null): void
    {
        if (!$this->canCancel()) {
            throw new \Exception('订单状态不允许取消');
        }

        DB::transaction(function () use ($reason) {
            $this->update([
                'status' => self::STATUS_CANCELLED,
                'cancelled_at' => now(),
                'cancel_reason' => $reason,
            ]);

            // 恢复库存
            $stockService = new \App\Services\StockService();
            foreach ($this->items as $item) {
                $stockService->restoreStock(
                    $item->product_id,
                    $item->variant_id,
                    $item->quantity
                );
            }
        });
    }


    /**
     * 获取最近的售后请求
     */
    public function getRecentAfterSales(int $limit = 3): \Illuminate\Database\Eloquent\Collection
    {
        return $this->afterSalesRequests()
            ->with(['items.orderItem.product'])
            ->latest()
            ->limit($limit)
            ->get();
    }

    /**
     * 查询作用域：待支付订单
     */
    public function scopePending($query)
    {
        return $query->where('status', self::STATUS_PENDING);
    }

    /**
     * 查询作用域：已支付订单
     */
    public function scopePaid($query)
    {
        return $query->where('payment_status', self::PAYMENT_PAID);
    }

    /**
     * 查询作用域：已发货订单
     */
    public function scopeShipped($query)
    {
        return $query->where('status', self::STATUS_SHIPPED);
    }

    /**
     * 查询作用域：已送达订单
     */
    public function scopeDelivered($query)
    {
        return $query->where('status', self::STATUS_DELIVERED);
    }

    /**
     * 查询作用域：已取消订单
     */
    public function scopeCancelled($query)
    {
        return $query->where('status', self::STATUS_CANCELLED);
    }

    /**
     * 查询作用域：可申请售后的订单
     */
    public function scopeCanApplyAfterSales($query)
    {
        return $query->whereIn('status', [
            self::STATUS_PROCESSING,
            self::STATUS_SHIPPED,
            self::STATUS_DELIVERED
        ])->where('payment_status', self::PAYMENT_PAID);
    }

    /**
     * 查询作用域：按用户筛选
     */
    public function scopeForUser($query, int $userId)
    {
        return $query->where('user_id', $userId);
    }

    /**
     * 查询作用域：按订单号搜索
     */
    public function scopeByOrderNumber($query, string $orderNumber)
    {
        return $query->where('order_number', 'like', "%{$orderNumber}%");
    }

    /**
     * 查询作用域：按商品名称搜索
     */
    public function scopeByProductName($query, string $productName)
    {
        return $query->whereHas('items', function ($q) use ($productName) {
            $q->where('product_name', 'like', "%{$productName}%");
        });
    }

    /**
     * 更新订单的售后相关状态
     */
    public function updateAfterSalesStatus(): void
    {
        if (!$this->hasAfterSales()) {
            return;
        }

        $stats = $this->getAfterSalesStats();
        
        // 如果有已完成的售后请求，更新扩展状态
        if ($stats['completed'] > 0) {
            if ($stats['completed'] === $stats['total']) {
                // 所有售后都已完成
                $this->update(['extended_status' => self::EXTENDED_STATUS_COMPLETED]);
            } else {
                // 部分售后已完成
                $this->update(['extended_status' => self::EXTENDED_STATUS_PARTIALLY_RETURNED]);
            }
        }
    }
}
